﻿/*******************************************************************************
 * Copyright © Chris Watson 2013                                               *
 *                                                                             *
 * This document is a part of the source code and related artefacts for Chris  *
 * Watson's Desktop Wallpaper Guard, a software application which will detect  *
 * when another process removes the wallpaper from a Windows desktop and       *
 * restore an image of the user's choice.                                      *
 *                                                                             *
 * Author:                                                                     *
 *   Chris Watson       [mailto:chris@watson.me.uk]                            *
 * Date:                                                                       *
 *   17 August 2013                                                            *
 ******************************************************************************/

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;

namespace Watson.BleaknessEliminator
{
    /// <summary>
    /// Contains P/Invoke methods.
    /// </summary>
    internal static class NativeMethods
    {
        #region Internal Constants

        /// <summary>
        /// Retrieves the full path of the bitmap file for the desktop
        /// wallpaper. The pvParam parameter must point to a buffer to receive
        /// the null-terminated path string. Set the uiParam parameter to the
        /// size, in characters, of the pvParam buffer. The returned string will
        /// not exceed MAX_PATH characters. If there is no desktop wallpaper,
        /// the returned string is empty.
        /// </summary>
        internal const int SPI_GETDESKWALLPAPER = 0x0073;
        
        /// <summary>
        /// A SPI_SETDESKWALLPAPER parameter for a WM_SETTINGCHANGE Windows
        /// message.
        /// </summary>
        internal const int SPI_SETDESKWALLPAPER = 20;


        /// <summary>
        /// Broadcasts the WM_SETTINGCHANGE message after updating the user
        /// profile.
        /// </summary>
        internal const int SPIF_SENDWININICHANGE = 0x02;


        /// <summary>
        /// Writes the new system-wide parameter setting to the user profile.
        /// </summary>
        internal const int SPIF_UPDATEINIFILE = 0x01;


        /// <summary>
        /// A WM_SETTINGCHANGE Windows message.
        /// </summary>
        internal const int WM_SETTINGCHANGE = 0x001A;
        
        #endregion

        #region Internal Methods

        /// <summary>
        /// Retrieves or sets the value of one of the system-wide parameters.
        /// This function can also update the user profile while setting a
        /// parameter.
        /// </summary>
        /// <param name="uAction">
        /// The system-wide parameter to be retrieved or set. 
        /// </param>
        /// <param name="uParam">
        /// A parameter whose usage and format depends on the system parameter
        /// being queried or set. For more information about system-wide
        /// parameters, see the uiAction parameter. If not otherwise indicated,
        /// you must specify zero for this parameter.
        /// </param>
        /// <param name="lpvParam">
        /// A parameter whose usage and format depends on the system parameter
        /// being queried or set. For more information about system-wide
        /// parameters, see the uiAction parameter. If not otherwise indicated,
        /// you must specify NULL for this parameter. For information on the
        /// PVOID datatype, see Windows Data Types.
        /// </param>
        /// <param name="fuWinIni">
        /// <para>
        /// If a system parameter is being set, specifies whether the user
        /// profile is to be updated, and if so, whether the WM_SETTINGCHANGE
        /// message is to be broadcast to all top-level windows to notify them
        /// of the change.
        /// </para>
        /// <para>
        /// This parameter can be zero if you do not want to update the user
        /// profile or broadcast the WM_SETTINGCHANGE message, or it can be one
        /// or more of the following values.
        /// </para>
        /// </param>
        /// <returns>
        /// System.Bool
        /// <para>
        /// If the function succeeds, the return value is a nonzero value. If
        /// the function fails, the return value is zero. To get extended error
        /// information, call <see cref="GetLastError"/>.
        /// </para>
        /// </returns>
        /// <remarks>
        /// Ref: http://msdn.microsoft.com/en-gb/library/windows/desktop/ms72494
        ///      7%28v=vs.85%29.aspx
        /// </remarks>
        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        [return: MarshalAs(UnmanagedType.Bool)]
        static internal extern bool SystemParametersInfo(
            int uAction, int uParam, string lpvParam, int fuWinIni); 
        
        #endregion
    }
}
